﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Xml;
using System.Xml.Linq;

namespace PLCS.App.LogManager.Service;

public class XmlDataConvert : IDataConvert
{
    private static List<PropertyNodeItem> GetElements(IEnumerable<XElement> xElements, string parentNodeName = "")
    {
        List<PropertyNodeItem> list = new List<PropertyNodeItem>();
        foreach (XElement item in xElements)
        {
            if (item.HasElements)
                list.Add(new PropertyNodeItem() { DisplayName = item.Name.ToString(), Children = GetElements(item.Elements(), item.Name.ToString()) });
            else
                list.Add(new PropertyNodeItem() { DisplayName = item.Name.ToString(), Value = item.Value.ToString() });
        }
        return list;
    }

    #region 优化前

    //public List<PropertyNodeItem> GetTreeModels(string data)
    //{
    //    data = data.Replace(@"<?xml version=""1.0"" encoding=""UTF-8""?>", string.Empty);
    //    data = data.Replace(@"<?xml version=""1.0""?>", string.Empty);
    //    XDocument xmlDocument = XDocument.Parse(data);
    //    IEnumerable<XElement> xElements = xmlDocument.Root!.Elements();
    //    IEnumerable<XElement> xElementfa = xmlDocument.Elements();
    //    string faNodeName = xElementfa.First().Name.ToString();

    //    return new List<PropertyNodeItem>() { new PropertyNodeItem() { DisplayName = faNodeName, Children = GetElements(xElements) } };
    //}

    #endregion 优化前

    /// <summary>
    /// 获取XML文档中的树模型
    /// </summary>
    /// <param name="data"></param>
    /// <returns></returns>
    public List<PropertyNodeItem> GetTreeModels(string data)
    {
        // 去除XML声明
        data = RemoveXmlDeclaration(data);

        // 解析XML文档
        XDocument xmlDocument = ParseXmlDocument(data);

        // 获取XML中根元素下的所有子元素
        IEnumerable<XElement> xElements = xmlDocument.Root.Elements();

        // 获取XML文档的根节点名称，如果没有则返回空字符串
        string faNodeName = xmlDocument.Elements().FirstOrDefault()?.Name.ToString() ?? string.Empty;

        // 返回树模型
        return new List<PropertyNodeItem>() { new PropertyNodeItem() { DisplayName = faNodeName, Children = GetElements(xElements) } };
    }

    /// <summary>
    /// 去除XML文档中的声明信息
    /// </summary>
    /// <param name="data"></param>
    /// <returns></returns>
    private string RemoveXmlDeclaration(string data)
    {
        return data.Replace(@"<?xml version=""1.0"" encoding=""UTF-8""?>", string.Empty)
                   .Replace(@"<?xml version=""1.0""?>", string.Empty);
    }

    /// <summary>
    /// 解析XML文档并返回XDocument实例
    /// </summary>
    /// <param name="data"></param>
    /// <returns></returns>
    private XDocument ParseXmlDocument(string data)
    {
        // 创建XmlReaderSettings对象，禁用DTD处理，提高安全性和性能
        XmlReaderSettings settings = new XmlReaderSettings();
        settings.DtdProcessing = DtdProcessing.Ignore;

        // 使用XmlReader解析XML文档并返回XDocument实例
        using (XmlReader reader = XmlReader.Create(new StringReader(data), settings))
        {
            return XDocument.Load(reader);
        }
    }
}